package com.uwlaser.service.impl;

import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.date.DateUtil;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.uwlaser.base.CommonTree;
import com.uwlaser.base.PageInfo;
import com.uwlaser.base.QueryHelpMybatisPlus;
import com.uwlaser.base.impl.CommonServiceImpl;
import com.uwlaser.domain.*;
import com.uwlaser.service.FactoryModelService;
import com.uwlaser.service.FactoryTreePathInfoService;
import com.uwlaser.service.RolesFactoryModelsServices;
import com.uwlaser.service.dto.*;
import com.uwlaser.service.mapper.*;
import com.uwlaser.utils.ConvertUtil;
import com.uwlaser.utils.PageUtil;
import com.uwlaser.utils.enums.DictValueEnum;
import lombok.AllArgsConstructor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Pageable;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.stream.Collectors;

// 默认不使用缓存
//import org.springframework.cache.annotation.CacheConfig;
//import org.springframework.cache.annotation.CacheEvict;
//import org.springframework.cache.annotation.Cacheable;

/**
 * @author QZK
 * @date 2022-05-11
 */
@Service
@AllArgsConstructor
// @CacheConfig(cacheNames = FactoryModelService.CACHE_KEY)
@Transactional(propagation = Propagation.SUPPORTS, readOnly = true, rollbackFor = Exception.class)
public class FactoryModelServiceImpl extends CommonServiceImpl<FactoryModelMapper, FactoryModel> implements FactoryModelService {

    // private final RedisUtils redisUtils;
    private final FactoryModelMapper factoryModelMapper;

    private final FactoryDeviceMainMapper factoryDeviceMainMapper;

    @Autowired
    private final FactoryTreePathInfoService factoryTreePathInfoService;

    private final RolesFactoryModelsServices rolesFactoryModelsServices;

    @Autowired
    private final FactoryShiftMapper factoryShiftMapper;

    @Autowired
    private final FactoryShiftTimeMapper factoryShiftTimeMapper;

    @Autowired
    private final FactoryTeamEmployeeMapper factoryTeamEmployeeMapper;

    @Autowired
    private final FactoryPlanHaltProductionMapper factoryPlanHaltProductionMapper;

    @Autowired
    private final FactoryShiftHistoryMapper factoryShiftHistoryMapper;


    private final SimpleDateFormat dateFormatYYYYMMDD = new SimpleDateFormat("yyyy-MM-dd");

    @Override
    public PageInfo<FactoryModelDto> queryAll(FactoryModelQueryParam query, Pageable pageable) {
        IPage<FactoryModel> queryPage = PageUtil.toMybatisPage(pageable);
        IPage<FactoryModel> page = factoryModelMapper.selectPage(queryPage, QueryHelpMybatisPlus.getPredicate(query));
        return ConvertUtil.convertPage(page, FactoryModelDto.class);
    }

    @Override
    public List<FactoryModelDto> queryAll(FactoryModelQueryParam query) {
        return ConvertUtil.convertList(factoryModelMapper.selectList(QueryHelpMybatisPlus.getPredicate(query)), FactoryModelDto.class);
    }

    @Override
    public FactoryModel getById(Integer id) {
        return factoryModelMapper.selectById(id);
    }

    @Override
    // @Cacheable(key = "'id:' + #p0")
    public FactoryModelDto findById(Integer id) {
        return ConvertUtil.convert(getById(id), FactoryModelDto.class);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int insert(FactoryModelDto resources) {
        FactoryModel entity = ConvertUtil.convert(resources, FactoryModel.class);

        //去重
        FactoryModel factoryModel = new FactoryModel();
        factoryModel.setModelCode(entity.getModelCode());
        factoryModel.setModelType(entity.getModelType());
        Integer count = factoryModelMapper.selectCount(new QueryWrapper<>(factoryModel));
        if (count >= 1) {
            throw new RuntimeException("模型编号【" + entity.getModelCode() + "】重复！");
        }
        factoryModelMapper.insert(entity);

        // 先往关系表加数据，再往主表加
        FactoryTreePathInfoDto treePathInfoDto;
        if (entity.getPid().equals(0)) {
            treePathInfoDto = FactoryTreePathInfoDto.builder().id(entity.getId()).build();
        } else {
            treePathInfoDto = FactoryTreePathInfoDto.builder().id(entity.getId()).ancestor(entity.getPid()).build();
        }
        int insert = factoryTreePathInfoService.insert(treePathInfoDto);
        //如果是设备则添加到设备表中
        addDevice(entity);
        return insert;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int updateById(FactoryModelDto resources) {
        FactoryModel entity = ConvertUtil.convert(resources, FactoryModel.class);

        //如果是设备需要更新设备列表
        FactoryModel old = factoryModelMapper.selectById(entity.getId());
        updateDevice(entity, old);

        int ret = factoryModelMapper.updateById(entity);
        //去重
        FactoryModel factoryModel = new FactoryModel();
        factoryModel.setModelCode(entity.getModelCode());
        factoryModel.setModelType(entity.getModelType());
        Integer count = factoryModelMapper.selectCount(new QueryWrapper<>(factoryModel));
        if (count >= 2) {
            throw new RuntimeException("模型编号【" + entity.getModelCode() + "】重复！");
        }
        // delCaches(resources.id);
        return ret;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int removeByIds(Set<Integer> ids) {
        // delCaches(ids);
        HashSet<Integer> modelIdList = new HashSet<>();
        for (Integer id : ids) {
            // 查出被删ID的所有子节点
            modelIdList.add(id);
            List<Integer> delIdList = factoryTreePathInfoService.queryAllFamily(FactoryTreePathInfo.builder().ancestor(id).build())
                    .stream().map(FactoryModel::getId).collect(Collectors.toList());
            modelIdList.addAll(delIdList);
            // 删除设备角色关系表数据
            rolesFactoryModelsServices.removeFactoryModelId(id);
        }
        //删除设备表数据
        delDevice(factoryModelMapper.selectBatchIds(modelIdList));
        factoryTreePathInfoService.removeByIds(ids);
        return factoryModelMapper.deleteBatchIds(modelIdList);
    }

    /**
     * 批量导入工厂模型
     *
     * @param resources
     * @return
     */
    @Transactional(rollbackFor = Exception.class)
    @Override
    public int importTree(List<CommonTree> resources) {
        //检测是否有相同的
        List<String> collect = resources.stream().map(CommonTree::getCode).collect(Collectors.toList());

        List<FactoryModel> factoryModels = factoryModelMapper.selectList(new LambdaQueryWrapper<FactoryModel>().in(FactoryModel::getModelCode, collect));
        if (factoryModels != null && factoryModels.size() > 0) {
            Set<Integer> ids = factoryModels.stream().map(FactoryModel::getId).collect(Collectors.toSet());
            //删除已存在的工厂及子节点
            removeByIds(ids);
        }
        //计数
        AtomicInteger atomicInteger = new AtomicInteger(0);

        //递归添加
        addModuleTree(resources, 0, atomicInteger);

        return atomicInteger.get();
    }

    @Override
    public List<FactoryModelDto> getFactoryModel(Integer pid) {
        List<FactoryModel> factoryModels;
        factoryModels = lambdaQuery().eq(FactoryModel::getPid, pid).orderByAsc(FactoryModel::getId).list();
        return ConvertUtil.convertList(factoryModels, FactoryModelDto.class);
    }

    @Override
    public Set<FactoryModel> getChildFactoryModels(List<FactoryModel> factoryModelList, Set<FactoryModel> factoryModelSet) {
        for (FactoryModel factoryModel : factoryModelList) {
            factoryModelSet.add(factoryModel);
            List<FactoryModel> factoryModels = lambdaQuery().eq(FactoryModel::getPid, factoryModel.getId()).list();
            if (CollectionUtil.isNotEmpty(factoryModels)) {
                getChildFactoryModels(factoryModels, factoryModelSet);
            }
        }
        return factoryModelSet;
    }

    /**
     * 获取工厂树结构
     *
     * @return
     */
    @Override
    public List<CommonTree> getTree() {
        //获取产品类型
        List<FactoryModel> models = factoryModelMapper.selectList(new LambdaQueryWrapper<FactoryModel>().orderByDesc(FactoryModel::getId));
        //构建树
        return buildTree(models);
    }

    /**
     * 获取工厂树结构（排除设备模型）
     *
     * @return
     */
    @Override
    public List<CommonTree> getTreeNotDevice() {
        //排除设备模型
        LambdaQueryWrapper<FactoryModel> queryWrapper = new LambdaQueryWrapper<FactoryModel>().ne(FactoryModel::getModelType, DictValueEnum.MODEL_TYPE_DEVICE.getValue()).orderByDesc(FactoryModel::getId);
        //获取产品类型
        List<FactoryModel> models = factoryModelMapper.selectList(queryWrapper);
        //构建树
        return buildTree(models);
    }

    /**
     * 构建树
     *
     * @param models
     * @return
     */
    public List<CommonTree> buildTree(List<FactoryModel> models) {
        if (models == null || models.size() == 0) {
            return new ArrayList<>();
        }
        //1.拿到最顶级的菜单列表数据
        List<FactoryModel> rootList = models.stream().filter(item -> item.getPid() == null || item.getPid() == 0)
                .collect(Collectors.toList());
        List<CommonTree> resList = new ArrayList<>();
        //2.递归思想，查找所有的子菜单树
        for (FactoryModel factoryModel : rootList) {
            CommonTree commonTree = getChildrens(models, factoryModel);
            resList.add(commonTree);
        }
        return resList;
    }

    /**
     * 根据ID获取工厂树
     *
     * @param id
     * @return
     */
    @Override
    public List<CommonTree> getTreeById(Integer id) {
        //根据ID获取所有节点
        FactoryTreePathInfo factoryTreePathInfo = new FactoryTreePathInfo();
        factoryTreePathInfo.setAncestor(id);
        List<FactoryModel> factoryModels = factoryTreePathInfoService.queryAllFamily(factoryTreePathInfo);

        //当前节点（父节点）
        FactoryModel factoryModel = factoryModels.stream().filter(node -> node.getId().equals(id)).findFirst().get();

        //组装树
        return Arrays.asList(getChildrens(factoryModels, factoryModel));
    }


    /**
     * 递归添加模型树
     *
     * @param resources
     * @param pid
     * @return
     */
    public void addModuleTree(List<CommonTree> resources, Integer pid, AtomicInteger atomicInteger) {
        //递归插入
        for (CommonTree resource : resources) {
            FactoryModel factoryModel = new FactoryModel();
            factoryModel.setModelType(resource.getType());
            factoryModel.setModelName(resource.getLabel());
            factoryModel.setModelCode(resource.getCode());
            factoryModel.setPid(pid);

            factoryModelMapper.insert(factoryModel);


            atomicInteger.incrementAndGet();
            // 先往关系表加数据，再往主表加
            FactoryTreePathInfoDto treePathInfoDto;
            if (factoryModel.getPid().equals(0)) {
                treePathInfoDto = FactoryTreePathInfoDto.builder().id(factoryModel.getId()).build();
            } else {
                treePathInfoDto = FactoryTreePathInfoDto.builder().id(factoryModel.getId()).ancestor(factoryModel.getPid()).build();
            }
            factoryTreePathInfoService.insert(treePathInfoDto);
            //如果是设备则添加到设备表中
            addDevice(factoryModel);

            if (resource.getChildren() != null && resource.getChildren().size() > 0) {
                addModuleTree(resource.getChildren(), factoryModel.getId(), atomicInteger);
            }
        }
    }

    /**
     * 添加设备列表
     *
     * @param factoryModel
     * @return
     */
    public int addDevice(FactoryModel factoryModel) {
        //判断是否是设备
        if (!factoryModel.getModelType().equals(DictValueEnum.MODEL_TYPE_DEVICE.getValue())) {
            return 0;
        }
        //查询所有父节点
        FactoryTreePathInfo factoryTreePathInfo = new FactoryTreePathInfo();
        factoryTreePathInfo.setDescendant(factoryModel.getId());
        List<FactoryModel> factoryModels = factoryTreePathInfoService.queryAllFamily(factoryTreePathInfo);
        HashMap<String, FactoryModel> modelMap = new HashMap<>();
        for (FactoryModel model : factoryModels) {
            modelMap.put(model.getModelType(), model);
        }
        FactoryDeviceMain deviceMain = new FactoryDeviceMain();
        deviceMain.setDeviceCode(factoryModel.getModelCode());
        deviceMain.setDeviceName(factoryModel.getModelName());
        //产线
        deviceMain.setLineCode(modelMap.get(DictValueEnum.MODEL_TYPE_LINE.getValue()).getModelCode());
        deviceMain.setSectionCode(modelMap.get(DictValueEnum.MODEL_TYPE_SECTION.getValue()).getModelCode());
        deviceMain.setStationCode(modelMap.get(DictValueEnum.MODEL_TYPE_STATION.getValue()).getModelCode());
        deviceMain.setDeviceType("1");
        deviceMain.setReceiveOrder(DictValueEnum.NO.getValue());
        deviceMain.setMonitor(DictValueEnum.YES.getValue());
        deviceMain.setDeviceGrade(DictValueEnum.DEVICE_GRADE_PIVOTAL.getValue());
        deviceMain.setUseState(DictValueEnum.USE_STATE_USE.getValue());
        //设置默认值
        deviceMain.setIsOnline(DictValueEnum.DEVICE_OFF_LINE.getValue());
        deviceMain.setDeviceStatus(DictValueEnum.DEVICE_STATUS_STOP.getValue());
        deviceMain.setAlarmCode("");
        //位置
        deviceMain.setPlace(
                modelMap.get(DictValueEnum.MODEL_TYPE_FACTROY.getValue()).getModelName() + "/"
                        + modelMap.get(DictValueEnum.MODEL_TYPE_WORKSHOP.getValue()).getModelName() + "/"
                        + modelMap.get(DictValueEnum.MODEL_TYPE_LINE.getValue()).getModelName() + "/"
                        + modelMap.get(DictValueEnum.MODEL_TYPE_SECTION.getValue()).getModelName() + "/"
                        + modelMap.get(DictValueEnum.MODEL_TYPE_STATION.getValue()).getModelName()
        );

        return factoryDeviceMainMapper.insert(deviceMain);
    }

    /**
     * 删除设备列表
     *
     * @param factoryModels
     * @return
     */
    public int delDevice(List<FactoryModel> factoryModels) {

        if (factoryModels == null || factoryModels.size() == 0) {
            return 0;
        }
        //判断是否是设备
        List<FactoryModel> devModel = factoryModels.stream().filter(item -> item.getModelType().equals(DictValueEnum.MODEL_TYPE_DEVICE.getValue())).collect(Collectors.toList());
        if (devModel == null || devModel.size() == 0) {
            return 0;
        }
        //得到设备编码
        List<String> codes = devModel.stream().map(FactoryModel::getModelCode).collect(Collectors.toList());

        //根据设备编码删除
        return factoryDeviceMainMapper.delete(new LambdaQueryWrapper<FactoryDeviceMain>().in(FactoryDeviceMain::getDeviceCode, codes));
    }

    /**
     * 更新设备列表
     *
     * @param factoryModel
     * @return
     */
    public int updateDevice(FactoryModel factoryModel, FactoryModel old) {
        if (factoryModel.getModelCode().equals(old.getModelCode()) && factoryModel.getModelName().equals(old.getModelName())) {
            return 0;
        }
        FactoryDeviceMain deviceMain = new FactoryDeviceMain();
        deviceMain.setDeviceCode(factoryModel.getModelCode());
        deviceMain.setDeviceName(factoryModel.getModelName());
        LambdaQueryWrapper<FactoryDeviceMain> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(FactoryDeviceMain::getDeviceCode, old.getModelCode());
        return factoryDeviceMainMapper.update(deviceMain, wrapper);
    }


    /**
     * 递归组装数据
     *
     * @param models
     * @param factoryModel
     * @return
     */
    private CommonTree getChildrens(List<FactoryModel> models, FactoryModel factoryModel) {
        CommonTree commonTree = toCommonTree(factoryModel);
        for (FactoryModel model : models) {
            if (model.getPid() != null && model.getPid().equals(factoryModel.getId())) {
                commonTree.getChildren().add(getChildrens(models, model));
            }
        }
        return commonTree;
    }

    /**
     * 转换对象
     *
     * @param factoryModel
     * @return
     */
    private CommonTree toCommonTree(FactoryModel factoryModel) {
        CommonTree commonTree = new CommonTree();
        commonTree.setType(factoryModel.getModelType());
        commonTree.setId(factoryModel.getId());
        commonTree.setCode(factoryModel.getModelCode());
        commonTree.setLabel(factoryModel.getModelName());
        commonTree.setChildren(new ArrayList<>());
        return commonTree;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int removeById(Integer id) {
        Set<Integer> set = new HashSet<>(1);
        set.add(id);
        return this.removeByIds(set);
    }

    @Override
    public ResponseEntity getCalendar(FactoryPlanHaltProductionDto resources) throws ParseException {
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM");
        //默认获取当前月份
        if (StringUtils.isEmpty(resources.getYears())) {
            resources.setYears(sdf.format(new Date()));
        }
        //获取当前工厂计划停机时间
        FactoryPlanHaltProduction factoryPlanHaltProduction = new FactoryPlanHaltProduction();
        factoryPlanHaltProduction.setTemplateCode(resources.getTemplateCode());
        List<FactoryPlanHaltProduction> factoryPlanHaltProductions = factoryPlanHaltProductionMapper.selectList(new QueryWrapper<>(factoryPlanHaltProduction));
        //记录休息日期
        Set<String> list = new HashSet<>();
        String years = resources.getYears();
        String[] split = years.split("-");
        //存在计划停机时,查看是否存在休息日
        if (!CollectionUtils.isEmpty(factoryPlanHaltProductions)) {
            //过滤出按周停机时间
            List<FactoryPlanHaltProduction> collect = factoryPlanHaltProductions.stream()
                    .filter(f -> f.getConfigType().equals("1") && f.getStartTime().equals("00:00") && f.getEndTime().equals("23:59")).collect(Collectors.toList());
            Map<String, String> monthFullDay = getMonthFullDay(Integer.parseInt(split[0]), Integer.parseInt(split[1]));

            //存在整天停机的定为休息日
            if (!CollectionUtils.isEmpty(collect)) {
                for (FactoryPlanHaltProduction planHaltProduction : collect) {
                    list.addAll(getDayOff(monthFullDay, planHaltProduction.getSpecifyTheWeek()));
                }
            }
            //获取指定时间为休息日的时间
            List<FactoryPlanHaltProduction> collect1 = factoryPlanHaltProductions.stream().filter(f -> f.getConfigType().equals("0") &&
                    f.getStartTime().split(" ")[1].equals("00:00:00") && f.getEndTime().split(" ")[1].equals("00:00:00")).collect(Collectors.toList());
            if (!CollectionUtils.isEmpty(collect1)) {
                for (FactoryPlanHaltProduction planHaltProduction : collect1) {
                    String[] s = planHaltProduction.getStartTime().split(" ");
                    String[] s1 = planHaltProduction.getEndTime().split(" ");
                    Date parse = DateUtil.parse(s[0], "yyyy-MM-dd");
                    Date parse1 = DateUtil.parse(s1[0], "yyyy-MM-dd");
                    if ((sdf.format(parse).equals(years) || sdf.format(parse1).equals(years)) && s1[0].compareTo(s[0]) > 0) {
                        //获取当月第一天
                        String lastFront = getLastFront(Integer.parseInt(split[0]), Integer.parseInt(split[1]));
                        //获取当月最后一天
                        String lastDay = getLastDay(Integer.parseInt(split[0]), Integer.parseInt(split[1]));
                        //获取时间段
                        //开始时间
                        String start = s[0].compareTo(lastFront) < 0 ? lastFront : s[0];
                        //结束时间
                        String finish = s1[0].compareTo(lastDay) > 0 ? lastDay : s1[0];
                        list.addAll(getBetweenDate(start, finish));
                    }
                }
            }
        }
        return new ResponseEntity(list, HttpStatus.OK);

    }

    @Override
    public ResponseEntity getCondition(FactoryShiftDto resources) {
        FactoryShift factoryShift = new FactoryShift();
        factoryShift.setTemplateCode(resources.getTemplateCode());
        factoryShift.setIsDisable("0");
        List<FactoryShift> factoryShifts = factoryShiftMapper.selectList(new QueryWrapper<>(factoryShift));
        List<FactoryShiftDto> list = new ArrayList<>();
        //存在点击日期，查询历史数据
        if (StringUtils.hasText(resources.getCurrentTime())) {
            List<FactoryShiftDto> historicalData = getHistoricalData(resources.getTemplateCode(), resources.getCurrentTime());
            if (CollectionUtil.isNotEmpty(historicalData)) {
                return new ResponseEntity(historicalData, HttpStatus.OK);
            }
        }

        if (!CollectionUtils.isEmpty(factoryShifts)) {
            //获取班次停机时间
            List<FactoryShiftTime> factoryShiftTimes = factoryShiftTimeMapper.selectList(new LambdaQueryWrapper<FactoryShiftTime>()
                    .in(FactoryShiftTime::getShiftId, factoryShifts.stream().map(FactoryShift::getId).collect(Collectors.toList()))
                    .eq(FactoryShiftTime::getIsDisable, "0"));
            //获取班组信息
            List<FactoryTeamEmployee> factoryTeamEmployees = factoryTeamEmployeeMapper.selectList(new LambdaQueryWrapper<FactoryTeamEmployee>()
                    .in(FactoryTeamEmployee::getTeamGroupId, factoryShifts.stream().map(FactoryShift::getTeamGroupId).collect(Collectors.toList())));


            for (FactoryShift shift : factoryShifts) {
                FactoryShiftDto convert = ConvertUtil.convert(shift, FactoryShiftDto.class);
                //获取班次停机信息
                if (!CollectionUtils.isEmpty(factoryShiftTimes)) {
                    //设置停机时间
                    convert.setFactoryShiftTimes(factoryShiftTimes.stream()
                            .filter(f -> f.getShiftId().equals(shift.getId())).collect(Collectors.toList()));

                }
                //获取班组信息
                if (!CollectionUtils.isEmpty(factoryTeamEmployees)) {
                    //设置班组信息
                    List<FactoryTeamEmployee> collect = factoryTeamEmployees.stream()
                            .filter(f -> f.getTeamGroupId().equals(shift.getTeamGroupId())).collect(Collectors.toList());
                    //设置班组负责人
                    if (!CollectionUtils.isEmpty(collect)) {
                        List<FactoryTeamEmployee> collect1 = collect.stream().filter(f -> f.getIsPrincipal().equals("1")).collect(Collectors.toList());
                        if (!CollectionUtils.isEmpty(collect1)) {
                            convert.setPrincipal(collect1.get(0).getEmployeeName());
                        }
                    }
                    convert.setFactoryTeamEmployees(collect);
                }
                list.add(convert);
            }
        }
        //获取计划停机信息
        return new ResponseEntity(list, HttpStatus.OK);
    }

    /**
     * 获取两个日期之间的所有日期 (年月日)
     *
     * @param startTime
     * @param endTime
     * @return
     */
    public static List<String> getBetweenDate(String startTime, String endTime) {
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        // 声明保存日期集合
        List<String> list = new ArrayList<String>();
        try {
            // 转化成日期类型
            Date startDate = sdf.parse(startTime);
            Date endDate = sdf.parse(endTime);

            //用Calendar 进行日期比较判断
            Calendar calendar = Calendar.getInstance();
            while (startDate.getTime() < endDate.getTime()) {
                // 把日期添加到集合
                list.add(sdf.format(startDate));
                // 设置日期
                calendar.setTime(startDate);
                //把日期增加一天
                calendar.add(Calendar.DATE, 1);
                // 获取增加后的日期
                startDate = calendar.getTime();
            }
        } catch (ParseException e) {
            e.printStackTrace();
        }
        return list;
    }

    /**
     * 某年某月的最后一天
     *
     * @param year
     * @param month
     * @return
     */
    public String getLastDay(int year, int month) {
        Calendar cal = Calendar.getInstance();
        cal.set(Calendar.YEAR, year);
        cal.set(Calendar.MONTH, month);
        cal.set(Calendar.DAY_OF_MONTH, 0); //关键！
        return DateUtil.formatDate(cal.getTime());
    }

    /**
     * 某年某月的第一天
     *
     * @param year
     * @param month
     * @return
     */
    public String getLastFront(int year, int month) {
        Calendar cal = Calendar.getInstance();
        cal.set(Calendar.YEAR, year);
        cal.set(Calendar.MONTH, month - 1);
        cal.set(Calendar.DAY_OF_MONTH, 1); //关键！
        return DateUtil.formatDate(cal.getTime());
    }

    /**
     * java 获取 获取某年某月 所有日期（yyyy-mm-dd格式字符串）
     *
     * @param year
     * @param month
     * @return
     */
    public Map<String, String> getMonthFullDay(int year, int month) {

        Map<String, String> map = new HashMap<>(32);
        // 获得当前日期对象
        Calendar cal = Calendar.getInstance();
        cal.clear();// 清除信息
        cal.set(Calendar.YEAR, year);
        // 1月从0开始
        cal.set(Calendar.MONTH, month - 1);
        // 当月1号
        cal.set(Calendar.DAY_OF_MONTH, 1);
        int count = cal.getActualMaximum(Calendar.DAY_OF_MONTH);
        for (int j = 1; j <= count; j++) {
            String dayOfWeek = getDayOfWeek(cal.get(Calendar.YEAR), cal.get(Calendar.MONTH) + 1, cal.get(Calendar.DAY_OF_MONTH));
            map.put(DateUtil.formatDate(cal.getTime()), dayOfWeek);
            cal.add(Calendar.DAY_OF_MONTH, 1);
        }
        return map;
    }

    /**
     * 获取某年某月某日 是 星期几
     *
     * @param year
     * @param month
     * @param day
     * @return
     */
    public String getDayOfWeek(int year, int month, int day) {
        //本地化
        Locale.setDefault(Locale.CHINA);
        String[] dayStringOfWeek = {"7", "1", "2", "3", "4", "5", "6"};
        Calendar cal = Calendar.getInstance();
        cal.set(Calendar.YEAR, year);
        cal.set(Calendar.MONTH, month - 1);
        cal.set(Calendar.DAY_OF_MONTH, day);
        // Java中Calendar.DAY_OF_WEEK其实表示：一周中的第几天，所以他会受到第一天是 星期一 还是 星期日 的影响
        int d = cal.get(Calendar.DAY_OF_WEEK);
        return dayStringOfWeek[d - 1];
    }

    /**
     * @return
     */
    public List<String> getDayOff(Map<String, String> map, String type) {
        List<String> list = new ArrayList<>();
        for (String s : map.keySet()) {
            if (map.get(s).equals(type)) {
                list.add(s);
            }
        }
        return list;
    }

    /**
     * 获取历史班次
     */
    public List<FactoryShiftDto> getHistoricalData(String templateCode, String currentTime) {
        //获取历史数据
        List<FactoryShiftHistory> factoryShiftHistories = factoryShiftHistoryMapper.selectList(new LambdaQueryWrapper<FactoryShiftHistory>()
                .eq(FactoryShiftHistory::getTemplateCode, templateCode).gt(FactoryShiftHistory::getDateTime, currentTime)
                .orderBy(true, true, FactoryShiftHistory::getCreateTime));
        if (!CollectionUtils.isEmpty(factoryShiftHistories)) {
            //获取日期数据
            List<String> collect = factoryShiftHistories.stream()
                    .map(FactoryShiftHistory::getDateTime).collect(Collectors.toList());
            //获取最小日期
            String min = CollectionUtil.min(collect);
            //获取当前日期的数据
            List<FactoryShiftHistory> collect1 = factoryShiftHistories.stream()
                    .filter(f -> min.equals(f.getDateTime())).collect(Collectors.toList());
            //判断数据当存在一个时返回当前数据，否则返回最大的数据
            if (collect1.size() == 1) {
                String dataJson = collect1.get(0).getDataJson();
                return JSONObject.parseArray(dataJson, FactoryShiftDto.class);
            }
            if (collect1.size() > 1) {
                String dataJson = collect1.get(collect1.size() - 1).getDataJson();
                return JSONObject.parseArray(dataJson, FactoryShiftDto.class);
            }

        }
        return null;
    }


    /*
    private void delCaches(Integer id) {
        redisUtils.delByKey(CACHE_KEY + "::id:", id);
    }

    private void delCaches(Set<Integer> ids) {
        for (Integer id: ids) {
            delCaches(id);
        }
    }*/

    /*
    @Override
    public void download(List<FactoryModelDto> all, HttpServletResponse response) throws IOException {
      List<Map<String, Object>> list = new ArrayList<>();
      for (FactoryModelDto factoryModel : all) {
        Map<String,Object> map = new LinkedHashMap<>();
              map.put("模型编码", factoryModel.getModelCode());
              map.put("模型名称", factoryModel.getModelName());
              map.put("模型类型", factoryModel.getModelType());
              map.put("独有类型", factoryModel.getUniqueType());
              map.put("理论节拍", factoryModel.getMeter());
              map.put("描述", factoryModel.getDescribes());
              map.put("上级ID", factoryModel.getPid());
              map.put("创建人", factoryModel.getCreateBy());
              map.put("创建时间", factoryModel.getCreateTime());
              map.put("更新人", factoryModel.getUpdateBy());
              map.put("更新时间", factoryModel.getUpdateTime());
        list.add(map);
      }
      FileUtil.downloadExcel(list, response);
    }*/
}
